package com.mars.module.admin.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.mars.common.response.PageInfo;
import com.mars.framework.context.ContextUserInfoThreadHolder;
import com.mars.module.admin.entity.*;
import com.mars.module.admin.mapper.*;
import com.mars.module.admin.request.SysDoctorRecordsRequest;
import com.mars.module.admin.request.SysMessageRequest;
import com.mars.module.admin.service.ISysDictDataService;
import com.mars.module.admin.service.ISysMessageService;
import com.mars.module.system.entity.SysUser;
import com.mars.module.system.entity.SysUserRole;
import com.mars.module.system.mapper.SysUserMapper;
import com.mars.module.system.mapper.SysUserRoleMapper;
import lombok.AllArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import com.mars.module.admin.request.SysVisitRecordsRequest;
import org.apache.commons.lang3.StringUtils;
import org.springframework.stereotype.Service;
import org.springframework.beans.BeanUtils;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.mars.module.admin.service.ISysVisitRecordsService;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.List;
import java.util.stream.Collectors;

/**
 * 患者就诊记录业务层处理
 *
 * @author caiJin
 * @date 2024-05-10
 */
@Slf4j
@Service
@AllArgsConstructor
public class SysVisitRecordsServiceImpl implements ISysVisitRecordsService {

    private final SysVisitRecordsMapper baseMapper;
    private final SysDoctorMapper doctorMapper;
    private final SysDepartmentMapper departmentMapper;
    private final SysHospitalMapper hospitalMapper;
    private final SysDoctorRecordsMapper doctorRecordsMapper;
    private final SysUserMapper userMapper;
    private final SysUserRoleMapper userRoleMapper;
    private final ISysDictDataService iSysDictDataService;
    private final ISysMessageService messageService;

    @Override
    @Transactional(rollbackFor = Exception.class)
    public SysVisitRecords add(SysVisitRecordsRequest request) {
        SysVisitRecords entity = SysVisitRecords.builder().build();
        BeanUtils.copyProperties(request, entity);
        Long userId = ContextUserInfoThreadHolder.get().getId();
        entity.setUserId(userId);
        entity.setStatus(1L);
        baseMapper.insert(entity);
        //增加医生出诊记录
        SysDoctorRecordsRequest doctorRecordsRequest = new SysDoctorRecordsRequest();
        SysDoctorRecords sysDoctorRecords = SysDoctorRecords.builder().build();
        doctorRecordsRequest.setDoctorId(request.getDoctorId());
        doctorRecordsRequest.setVisitDate(request.getVisitDate());
        doctorRecordsRequest.setVisitId(entity.getId());
        doctorRecordsRequest.setStatus("0");
        BeanUtils.copyProperties(request, sysDoctorRecords);
        doctorRecordsMapper.insert(sysDoctorRecords);
        //增加消息提醒
        SysDoctor doctor = doctorMapper.selectById(request.getDoctorId());
        SysMessageRequest messageRequest = new SysMessageRequest();
        messageRequest.setContent("您预约了【" + request.getVisitDate() + "】【" + doctor.getName() + "】医生的就诊记录，请及时就诊！");
        messageRequest.setReceiver(userId);
        messageRequest.setSender(1000000000000000001L);
        messageRequest.setStatus(0);
        messageRequest.setTitle("就诊提醒");
        messageService.add(messageRequest);
        return entity;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean delete(Long id) {
        return baseMapper.deleteById(id) > 0;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean deleteBatch(List<Long> ids) {
        return baseMapper.deleteBatchIds(ids) > 0;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public boolean update(SysVisitRecordsRequest request) {
        SysVisitRecords entity = SysVisitRecords.builder().build();
        BeanUtils.copyProperties(request, entity);
        return baseMapper.updateById(entity) > 0;
    }

    @Override
    public SysVisitRecords getById(Long id) {
        SysVisitRecords sysVisitRecords = baseMapper.selectById(id);
        SysDoctor doctor = doctorMapper.selectById(sysVisitRecords.getDoctorId());
        SysDepartment department = departmentMapper.selectById(doctor.getDepartmentId());
        SysHospital sysHospital = hospitalMapper.selectById(department.getHospitalId());
        sysVisitRecords.setFullName(doctor.getName() + "-" + department.getName() + "-" + sysHospital.getName());
        return sysVisitRecords;
    }

    @Override
    public PageInfo<SysVisitRecords> pageList(SysVisitRecordsRequest request) {
        Page<SysVisitRecords> page = new Page<>(request.getPageNo(), request.getPageSize());
        LambdaQueryWrapper<SysVisitRecords> query = this.buildWrapper(request);
        IPage<SysVisitRecords> pageRecord = baseMapper.selectPage(page, query);
        List<SysVisitRecords> records = pageRecord.getRecords();
        List<SysVisitRecords> recordsNew = new ArrayList<>();
        Long userId = ContextUserInfoThreadHolder.get().getId();
        for (SysVisitRecords e : records) {
            Long l = userRoleMapper.selectCount(new QueryWrapper<SysUserRole>().eq("user_id", userId).eq("role_id", "1052613170658541568"));
            if (l > 0) {
                e.setIsAdmin("1");
            }
            if (userId.equals(e.getUserId())) {
                e.setIsCurrent("1");
            } else {
                e.setIsCurrent("0");
            }
            SysUser sysUser = userMapper.selectById(e.getUserId());
            e.setUserName(sysUser == null ? "" : sysUser.getUserName());
            SysDoctor doctor = doctorMapper.selectById(e.getDoctorId());
            e.setDoctorName(doctor == null ? "" : doctor.getName());
            e.setStatusName(iSysDictDataService.getDictDataById("visit_type", e.getStatus().toString()));
            recordsNew.add(e);
        }
        pageRecord.setRecords(recordsNew);
        return PageInfo.build(pageRecord);
    }


    @Override
    public List<SysVisitRecords> list(SysVisitRecordsRequest request) {
        LambdaQueryWrapper<SysVisitRecords> query = this.buildWrapper(request);
        return baseMapper.selectList(query);
    }

    @Override
    public boolean cancel(Long[] ids) {
        SysVisitRecords sysVisitRecords = baseMapper.selectById(ids[0]);
        sysVisitRecords.setStatus(2L);
        SysDoctor doctor = doctorMapper.selectById(sysVisitRecords.getDoctorId());
        if (doctor != null) {
            doctor.setIsFree("1");
            doctorMapper.updateById(doctor);
        }
        baseMapper.updateById(sysVisitRecords);
        //增加消息提醒
        SysMessageRequest messageRequest = new SysMessageRequest();
        messageRequest.setContent("您预约了" + sysVisitRecords.getVisitDate() + "的就诊记录，已被管理员取消！");
        messageRequest.setReceiver(sysVisitRecords.getUserId());
        messageRequest.setSender(1000000000000000001L);
        messageRequest.setStatus(0);
        messageRequest.setTitle("挂号取消提醒");
        messageService.add(messageRequest);
        //删除医生出诊记录
        SysDoctorRecords sysDoctorRecords = doctorRecordsMapper.selectList(new QueryWrapper<SysDoctorRecords>().eq("doctor_id", sysVisitRecords.getDoctorId())
                .eq("visit_date", sysVisitRecords.getVisitDate())).stream().findFirst().orElse(null);
        if (sysDoctorRecords != null) {
            sysDoctorRecords.setStatus("0");
        }
        return doctorRecordsMapper.updateById(sysDoctorRecords) > 0;
    }

    private LambdaQueryWrapper<SysVisitRecords> buildWrapper(SysVisitRecordsRequest param) {
        LambdaQueryWrapper<SysVisitRecords> query = new LambdaQueryWrapper<>();
        if (StringUtils.isNotBlank(param.getHome())) {
            query.like(SysVisitRecords::getHome, param.getHome());
        }
        if (StringUtils.isNotBlank(param.getDisease())) {
            query.like(SysVisitRecords::getDisease, param.getDisease());
        }
        if (param.getVisitDate() != null) {
            query.like(SysVisitRecords::getVisitDate, param.getVisitDate());
        }
        if (param.getUserId() != null) {
            query.like(SysVisitRecords::getUserId, param.getUserId());
        }
        if (param.getDoctorId() != null) {
            query.like(SysVisitRecords::getDoctorId, param.getDoctorId());
        }
        if (param.getStatus() != null) {
            query.like(SysVisitRecords::getStatus, param.getStatus());
        }
        return query;
    }

}
